
package ConwaysGameOfLife;

import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Point;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
import java.util.ArrayList;
import javax.swing.JDesktopPane;

/**
 *
 * @author Bryan
 */

//This class is responsible for drawing all cell interactions onto the main board!!
public class JDesktopInternal extends JDesktopPane implements MouseListener, MouseMotionListener, Runnable {

    private final WorldControlMediator mediator;
    private Color backgroundColor = Color.black;
    //isSpawning declares whether or not there are cells being birthed
    private boolean isSpawning = false;
    private Point mousePosition;

    public JDesktopInternal(WorldControlMediator mediator) {
        this.mediator = mediator;
        addMouseMotionListener(this);
        addMouseListener(this);
        this.setBackground(Color.red);
    }

    public JDesktopInternal() {
        mediator = null;
    }

    @Override
    //responsible for painting all cells on the board
    public void paintComponent(Graphics g) {
        //super.paintComponent(g);
        Cell[][] world = mediator.getWorld();
        ArrayList<Cell> liveCells = mediator.getLivingCells();
        //this creates a local copy of living cells to avoid Co-Modification
        Cell[] convertedCells = new Cell[liveCells.size()];
        convertedCells = liveCells.toArray(convertedCells);
        g.setColor(backgroundColor);
        g.fillRect(0, 0, getWidth(), getHeight());

        //draws all cells to the board
        if (mediator.isWorldInitialized()) {
            double xMult = getWidth() / world.length;
            double yMult = getHeight() / world[0].length;
            for (Cell cell : convertedCells) {
                g.setColor(mediator.getBrushColor());
                g.fillRect((int) (cell.getLocation().x * xMult), (int) (cell.getLocation().y * yMult), (int) xMult, (int) yMult);
                g.setColor(mediator.getBrushColor().darker());
                g.drawRect((int) (cell.getLocation().x * xMult), (int) (cell.getLocation().y * yMult), (int) xMult, (int) yMult);
            }
        }
        repaint();
    }

    @Override
    public void mouseClicked(MouseEvent e) {
        //System.out.println("mouseClick");
    }

    @Override
    //start spawning new cells at mouse location
    //and begins thread that adds new births to a list
    public void mousePressed(MouseEvent e) {
        if (mediator.isWorldInitialized()) {
            isSpawning = true;
            mousePosition = e.getPoint();
            new Thread(this).start();
        }

    }

    @Override
    //disables spawning and subsequently kills spawn thread
    public void mouseReleased(MouseEvent e) {
        if (mediator.isWorldInitialized()) {
            mousePosition = e.getPoint();
            isSpawning = false;
        }
    }

    @Override
    public void mouseEntered(MouseEvent e) {
        // System.out.println("mouseEntered");
    }

    @Override
    public void mouseExited(MouseEvent e) {
        //System.out.println("mouseExited");
    }

    @Override
    //reports location of mouse to spawn new cells
    public void mouseDragged(MouseEvent e) {
        if (mediator.isWorldInitialized()) {
            mousePosition = e.getPoint();
            isSpawning = true;
        }
    }

    @Override
    public void mouseMoved(MouseEvent e) {
        //System.out.println("mouseMoved");
    }

    //responsible for generating a list of new cells to spawn that is
    //sent to worldControl every tick based on game speed
    private void spawnCells() {
        while (isSpawning) {     
            Point cellPosition = new Point((int) (mousePosition.x / (getWidth() / mediator.getWorld().length)), (int) (mousePosition.y / (getHeight() / mediator.getWorld()[0].length)));
            mediator.birthCell(mediator.getCell(cellPosition, mediator.getWorld()), mediator.getLivingCellsToAdd());
        }
    }

    @Override
    public void run() {
        spawnCells();
    }

    public Color getBackgroundColor() {
        return backgroundColor;
    }

    public void setBackgroundColor(Color backgroundColor) {
        this.backgroundColor = backgroundColor;
    }

}
